<template>
  <div id="cesiumContainer" ref="cesiumContainer"></div>
</template>

<script setup>
import * as Cesium from 'cesium'
import { onMounted, ref } from 'vue'
import earthImg from '../assets/earth2.jpg'
import icon from '../assets/wind.png'
import { GlobeRotate } from '../utils/globeRotate.js'
import apngjs from '../utils/apngjs.js'
// 设置cesium token
Cesium.Ion.defaultAccessToken =
  'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJqdGkiOiJhMzNkNTE5Zi1mMjY4LTRiN2QtOTRlZC1lOTUyM2NhNDYzNWYiLCJpZCI6NTU0OTYsImlhdCI6MTYyNTAyNjMyOX0.a2PEM4hQGpeuMfeB9-rPp6_Gkm6O-02Dm4apNbv_Dlk'

let viewer = null
onMounted(() => {
  viewer = new Cesium.Viewer('cesiumContainer', {
    animation: false, //是否创建动画小器件，左下角仪表
    baseLayerPicker: false, //是否显示图层选择器
    fullscreenButton: false, //是否显示全屏按钮
    geocoder: false, //是否显示geocoder小器件，右上角查询按钮
    homeButton: false, //是否显示Home按钮
    infoBox: false, //是否显示信息框
    sceneModePicker: false, //是否显示3D/2D选择器
    selectionIndicator: false, //是否显示选取指示器组件
    timeline: false, //是否显示时间轴
    sceneMode: Cesium.SceneMode.SCENE3D, //设定3维地图的默认场景模式:Cesium.SceneMode.SCENE2D、Cesium.SceneMode.SCENE3D、Cesium.SceneMode.MORPHING
    navigationHelpButton: false, //是否显示右上角的帮助按钮
    scene3DOnly: true, //如果设置为true，则所有几何图形以3D模式绘制以节约GPU资源
    navigationInstructionsInitiallyVisible: false,
    showRenderLoopErrors: false, //是否显示渲染错误
    orderIndependentTranslucency: false,
    imageryProvider: new Cesium.SingleTileImageryProvider({
      url: earthImg
    })
  })

  // Globe 对象
  let globe = viewer.scene.globe
  // 一定要为 true，否则 undergroundColor 设置无效
  globe.translucency.enabled = true
  // 基础色透明，默认是蓝色 Cesium.Color.BLUE
  globe.baseColor = Cesium.Color.BLACK
  // 地下色透明，默认是黑色 Cesium.Color.BLACK
  globe.undergroundColor = Cesium.Color.TRANSPARENT
  globe.atmosphereLightIntensity = 0
  // 隐藏天空大气层，否则最外围有一圈
  viewer.scene.skyAtmosphere.show = false

  // 设置相机位置
  viewer.camera.setView({
    // Cesium的坐标是以地心为原点，一向指向南美洲，一向指向亚洲，一向指向北极州
    // fromDegrees()方法，将经纬度和高程转换为世界坐标
    destination: Cesium.Cartesian3.fromDegrees(180.0, 15.0, 18000000.0)
    // orientation: {
    //   heading: Cesium.Math.toRadians(90, 0),// 指向
    //   pitch: Cesium.Math.toRadians(-90), // 视角
    //   roll: 0.5
    // }
  })

  // 创建一个圆环线的位置数组==============================
  let positionsRing = []
  let speed = 2 // 控制线的密度，你可以根据需要调整
  let amplitude = 10 // 上下往复的幅度，你可以根据需要调整
  for (let i = 0; i <= 360; i += speed) {
    positionsRing.push(i) // 通过改变 i 的步长来改变线的密度
    positionsRing.push(amplitude * Math.sin(Cesium.Math.toRadians(i))) // 使用正弦函数改变纬度，实现上下往复的运动
    positionsRing.push(4000000.0)
  }
  console.log('log--> positionsRing', positionsRing)

  let point = viewer.entities.add({
    position: new Cesium.CallbackProperty(function () {
      let time = viewer.clock.currentTime.secondsOfDay / 2
      let newPositionsRing = positionsRing.map((value, index) => {
        if (index % 3 === 0) {
          return value + (1 - Math.cos(time / 100000)) * 30
        }
        return value
      })
      let index = Math.floor((time / 10000) * (newPositionsRing.length / 3)) * 3
      index = index % newPositionsRing.length

      return Cesium.Cartesian3.fromDegrees(
        newPositionsRing[index],
        newPositionsRing[index + 1],
        newPositionsRing[index + 2]
      )
    }, false),
    point: {
      pixelSize: 15,
      color: Cesium.Color.TAN.withAlpha(0.8)
    }
  })

  let orbit = viewer.entities.add({
    polyline: {
      positions: new Cesium.CallbackProperty(function () {
        let time = viewer.clock.currentTime.secondsOfDay / 2

        let newPositionsRing = positionsRing.map((value, index) => {
          // 每一帧都更新经度，使线看起来像在旋转
          if (index % 3 === 0) {
            return value + (1 - Math.cos(time / 100000)) * 30
          }
          return value
        })

        return Cesium.Cartesian3.fromDegreesArrayHeights(newPositionsRing)
      }, false),
      width: 2,
      material: Cesium.Color.TAN.withAlpha(0.3)
    }
  })
  // 创建一个圆环线的位置数组==============================

  // 地球球体自转
  let globeRotate = new GlobeRotate(viewer)
  globeRotate.start()

  /*
  // 地球球体自转 开启 tick
  viewer.clock.shouldAnimate = true
  //每次旋转的弧度 越小越慢
  var angle = Cesium.Math.toRadians(Math.PI * 0.1)
  // 旋转次数 用来控制停止
  var rotate_num = 0
  function onTickCallback() {
    viewer.scene.camera.rotate(Cesium.Cartesian3.UNIT_Z, angle)
    //以下用来控制 停止
    rotate_num++
    // 110 次旋转一周
    // if (rotate_num === 110) {
    //   //结束旋转
    //   viewer.clock.onTick.removeEventListener(onTickCallback)
    //   //可以再接定位动画
    //   // viewer.camera.flyTo({......})
    // }
  }
  // 利用时钟进行监听
  viewer.clock.onTick.addEventListener(onTickCallback)
 */

  /* 
  //  生成64800个点，每个经度、纬度值各生成一个点，高度为0（贴地表）
  //  每个点都添加到PointPrimitiveCollection对象中
  for (var longitude = -180; longitude < 180; longitude++) {
    var color = Cesium.Color.PINK
    if (longitude % 2 === 0) {
      color = Cesium.Color.CYAN
    }
    for (var latitude = -90; latitude < 90; latitude++) {
      pointCollection.add({
        position: Cesium.Cartesian3.fromDegrees(longitude, latitude),
        color: color
      })
    }
  }

  //  模拟每个点固定向外偏移(1km,1km,1km)(跟时间无关，每帧调用此函数)
  function animatePoints() {
    var positionScratch = new Cesium.Cartesian3()
    var points = pointCollection._pointPrimitives
    var length = points.length
    for (var i = 0; i < length; ++i) {
      var point = points[i]
      Cesium.Cartesian3.clone(point.position, positionScratch)
      Cesium.Cartesian3.add(
        positionScratch,
        new Cesium.Cartesian3(1000, 1000, 1000),
        positionScratch
      )
      point.position = positionScratch
    }
  }

  //  scene中的render 方法，每一帧都被会调用，用于场景的重绘
  //  此处的preRender在render方法之前执行，也是每一帧被调用
  //  由于每一帧调用animatePoints方法时，方法内部都将每个点
  //    的位移向外移动1km，因此所有点就都运动起来了
  viewer.scene.preRender.addEventListener(animatePoints)
 */

  /* 
  
  // 粒子

  //   particleSystem : {
  //     image : '../../SampleData/fire.png',
  //     emissionRate: 50.0,
  //     emitter: new Cesium.SphereEmitter(5.0)
  // }

  var particleSystem = viewer.scene.primitives.add(
    new Cesium.ParticleSystem({
      image: star,
      imageSize: new Cesium.Cartesian2(20, 20),
      startScale: 1.0,
      endScale: 4.0,
      particleLife: 10.0,
      speed: 1.0,
      emitter: new Cesium.CircleEmitter(0.5),
      emissionRate: 5.0,
      // modelMatrix: entity.computeModelMatrix(
      //   viewer.clock.startTime,
      //   new Cesium.Matrix4()
      // ),
      lifetime: 16.0,
      forces: [applyGravity]
    })
  )

  // // 创建粒子系统
  // let particleSystem = viewer.scene.primitives.add(
  //   new Cesium.ParticleSystem({
  //     image: star, // 粒子的图像
  //     startColor: Cesium.Color.YELLOW, // 粒子的初始颜色
  //     endColor: Cesium.Color.YELLOW, // 粒子的结束颜色
  //     startScale: 1.0, // 粒子的初始大小
  //     endScale: 2.0, // 粒子的结束大小
  //     minimumParticleLife: 1.0, // 粒子的最小生命周期
  //     maximumParticleLife: 2.0, // 粒子的最大生命周期
  //     minimumSpeed: 0.01, // 粒子的最小速度
  //     maximumSpeed: 0.05, // 粒子的最大速度
  //     imageSize: new Cesium.Cartesian2(20, 20), // 粒子的图像大小
  //     emissionRate: 5.0, // 每秒发射的粒子数量
  //     lifetime: 16.0, // 粒子系统的生命周期
  //     emitter: new Cesium.SphereEmitter(10000000.0), // 粒子发射器，这里我们使用一个球形发射器，半径为5000000.0
  //     forces: [applyGravity] // 粒子受到的力，这里我们添加了重力
  //   })
  // )


  let points = viewer.scene.primitives.add(
    new Cesium.PointPrimitiveCollection()
  )

  // 创建点粒子
  function createPoint() {
    let point = points.add({
      color: Cesium.Color.YELLOW,
      pixelSize: 5,
      position: new Cesium.Cartesian3(
        Math.random() * 2 - 1,
        Math.random() * 2 - 1,
        Math.random() * 2 - 1
      )
    })

    // 设置点粒子的运动
    point.velocity = new Cesium.Cartesian3(
      Math.random() * 0.02 - 0.01,
      Math.random() * 0.02 - 0.01,
      Math.random() * 0.02 - 0.01
    )

    return point
  }

  // 创建多个点粒子
  for (let i = 0; i < 1000; i++) {
    createPoint()
  }

  // 更新点粒子的位置
  viewer.scene.preRender.addEventListener(function () {
    for (let i = 0; i < points.length; i++) {
      let point = points.get(i)
      point.position = Cesium.Cartesian3.add(
        point.position,
        point.velocity,
        new Cesium.Cartesian3()
      )
    }
  })

  // // 重力函数
  function applyGravity(p, dt) {
    // 我们将重力定向到地球的中心
    var position = p.position
    var gravity = Cesium.Cartesian3.normalize(position, new Cesium.Cartesian3())
    Cesium.Cartesian3.multiplyByScalar(gravity, -9.8 * dt, gravity)
    p.velocity = Cesium.Cartesian3.add(p.velocity, gravity, p.velocity)
  }

  // viewer.primitives.add(
  //   new Cesium.ParticleSystem({
  //     image: star,
  //     color: Cesium.Color.MAGENTA,
  //     emissionRate: 5.0,
  //     emitter: new Cesium.SphereEmitter(5.0),
  //     imageSize: new Cesium.Cartesian2(25.0, 25.0),
  //     modelMatrix: entity.computeModelMatrix(
  //       viewer.clock.startTime,
  //       new Cesium.Matrix4()
  //     ),
  //     lifetime: 16.0
  //   })
  // )

  
  
  */

  /* 
   // viewer.entities.add({
  //   show: true,
  //   position: Cesium.Cartesian3.fromDegrees(119.39, 39.9, 0),
  //   ellipse: {
  //     semiMinorAxis: 80000.0,
  //     semiMajorAxis: 80000.0,
  //     material: new Cesium.ImageMaterialProperty({
  //       image: star, // 图片以材质的方式填充
  //       color: Cesium.Color.RED,
  //       repeat: new Cesium.Cartesian2(10, 10)
  //     }),

  //     // rotation: 45,
  //     // 利用下面这个属性设置素材填充时的选装角度（顺时针方向）
  //     stRotation: 45
  //   }
  // })

 
 */

  /* 

 // 点
  let yellowPoints = viewer.scene.primitives.add(
    new Cesium.PointPrimitiveCollection()
  )
  let radius = 50 // 半径，可以根据需要调整
  let angleStep = (2 * Math.PI) / 10 // 分成10份

  function addPoint() {
    let center = viewer.camera.position
    for (let i = 0; i < 10; i++) {
      let angle = Math.random() * angleStep
      let x = center.x + radius * Math.cos(angle)
      let y = center.y + radius * Math.sin(angle)
      let point = yellowPoints.add({
        position: new Cesium.Cartesian3(x, y, center.z),
        color: Cesium.Color.YELLOW,
        pixelSize: 10, // 点的初始大小，可以根据需要调整
        heightReference: Cesium.HeightReference.RELATIVE_TO_GROUND // 提高点的显示层级
      })
      point.lifetime = Date.now() + 10000 // 点的生命周期为10秒
    }
  }

  addPoint()
  let intervalId = setInterval(addPoint, 1000 / 3) // 每秒生成3个点

  function animatePoints() {
    var points = yellowPoints._pointPrimitives
    var length = points.length
    for (var i = 0; i < length; ++i) {
      var point = points[i]
      point.position = Cesium.Cartesian3.add(
        point.position,
        new Cesium.Cartesian3(1000, 1000, 1000),
        new Cesium.Cartesian3()
      )
      point.pixelSize += 0.01 // 点的大小逐渐变大
      if (Date.now() > point.lifetime) {
        yellowPoints.remove(point) // 当点的生命周期结束时，从集合中移除它
      }
    }
  }

  viewer.scene.preRender.addEventListener(animatePoints)

  // 设置地球透明
  viewer.scene.globe.alpha = 0
  
  */
})
</script>

<style>
* {
  margin: 0;
  padding: 0;
}
#cesiumContainer {
  width: 100vw;
  height: 100vh;
}
</style>
